package com.sky.service.impl;

import com.sky.dto.OrderCountDto;
import com.sky.dto.TopDto;
import com.sky.entity.Orders;
import com.sky.mapper.ReportMapper;
import com.sky.service.ReportService;
import com.sky.vo.*;
import io.swagger.models.auth.In;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang.StringUtils;
import org.apache.http.HttpResponse;
import org.apache.poi.xssf.usermodel.XSSFRow;
import org.apache.poi.xssf.usermodel.XSSFSheet;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Service
@Slf4j
public class ReportServiceImpl implements ReportService {
    @Autowired
    private ReportMapper reportMapper;
    @Autowired
    private WorkspaceServiceImpl workspaceService;

    /**
     * 获取日期集合
     * @param begin
     * @param end
     * @return
     */
    List<LocalDate> getDateList(LocalDate begin,LocalDate end){
        List<LocalDate> dateList = new ArrayList<>();//存放时间的集合
        //获取日期集合
        dateList.add(begin);
        while (!begin.equals(end)){
            begin=begin.plusDays(1);
            dateList.add(begin);
        }
        return dateList;
    }

    @Override
    public TurnoverReportVO turnoverStatistics(LocalDate begin, LocalDate end) {
        List<Double> moneyList = new ArrayList<>();
        //获取日期集合
        List<LocalDate> dateList = getDateList(begin, end);
        dateList.forEach(date->{
            LocalDateTime beginTime = LocalDateTime.of(date, LocalTime.MIN);
            LocalDateTime endTime = LocalDateTime.of(date, LocalTime.MAX);
            Map map = new HashMap();
            map.put("beginTime",beginTime);
            map.put("endTime",endTime);
            map.put("status", Orders.COMPLETED);
            Double money=reportMapper.turnoverStatistics(map);
            money = money == null ? 0 : money;
            moneyList.add(money);
        });
        //封装数据
        TurnoverReportVO vo = TurnoverReportVO.builder()
                .dateList(StringUtils.join(dateList, ","))
                .turnoverList(StringUtils.join(moneyList, ","))
                .build();
        return vo;
    }
    /**
     * 新增用户统计
     * @param begin
     * @param end
     * @return
     */
    @Override
    public UserReportVO userStatistics(LocalDate begin, LocalDate end) {
        List<Integer> totalUSerList = new ArrayList<>();//存放总用户的集合
        List<Integer> newlUSerList = new ArrayList<>();//存放每日注册用户的集合
        //获取日期集合
        List<LocalDate> dateList = getDateList(begin, end);
        dateList.forEach(date->{
            LocalDateTime start = LocalDateTime.of(date, LocalTime.MIN);
            LocalDateTime last = LocalDateTime.of(date, LocalTime.MAX);
            //查询每天注册的用户
            Integer total=reportMapper.userStatistics(start,last);
            Integer sum = reportMapper.userTotal(last);
            total=total==null ? 0 :total;
            sum=sum==null ? 0 :sum;
            newlUSerList.add(total);
            totalUSerList.add(sum);
        });
        return UserReportVO
                .builder()
                .dateList(StringUtils.join(dateList,","))
                .newUserList(StringUtils.join(newlUSerList,","))
                .totalUserList(StringUtils.join(totalUSerList,","))
                .build();
    }

    /**
     * 订单完成率统计接口
     * @param begin
     * @param end
     * @return
     */
    @Override
    public OrderReportVO ordersStatistics(LocalDate begin, LocalDate end) {
        List<Integer> orderCountList =new ArrayList<>();//每日订单数
        List<Integer> datevalidOrderCountListList =new ArrayList<>();//每日有效订单数
        //获取日期集合
        List<LocalDate> dateList = getDateList(begin, end);
        //遍历集合获取每日的订单数及有效订单数
        dateList.forEach(list->{
            LocalDateTime start = LocalDateTime.of(list, LocalTime.MIN);
            LocalDateTime last = LocalDateTime.of(list, LocalTime.MAX);
            //获取当天的订单数
            Integer total = reportMapper.getOrdersByLimit(
                            OrderCountDto.builder()
                            .begin(start)
                            .last(last)
                            .build());
            total=total==null ? 0 : total;
            orderCountList.add(total);
            // 获取当天的有效订单数
            Integer validOrderCount = reportMapper.getOrdersByLimit(
                                      OrderCountDto.builder()
                                      .begin(start)
                                      .last(last)
                                      .status(Orders.COMPLETED)
                                      .build()
            );
            validOrderCount=validOrderCount==null ? 0 :validOrderCount;
            datevalidOrderCountListList.add(validOrderCount);
            log.info("当天订单:{},有效订单:{}",total,validOrderCount);

        });
        //获取总的订单数
        Integer allOrders = reportMapper.getOrdersByLimit(new OrderCountDto());
        //获取总的有效订单数
        Integer allValidOrders = reportMapper.getOrdersByLimit( OrderCountDto
                                        .builder()
                                        .status(Orders.COMPLETED)
                                        .build());
        //订单完成率
        Double orderCompletionRate=0.0;
        if(allOrders!=0){
            orderCompletionRate=allValidOrders.doubleValue()/allOrders;
        }
        return OrderReportVO
                .builder()
                .dateList(StringUtils.join(dateList,","))
                .orderCountList(StringUtils.join(orderCountList,","))
                .validOrderCountList(StringUtils.join(datevalidOrderCountListList,","))
                .totalOrderCount(allOrders)
                .validOrderCount(allValidOrders)
                .orderCompletionRate(orderCompletionRate)
                .build();

    }


    /**
     * 获取每日销售前十的菜品
     * @param begin
     * @param end
     * @return
     */
    @Override
    public SalesTop10ReportVO getTop10(LocalDate begin, LocalDate end) {
        List<String> nameList = new ArrayList<>();//菜品名称集合
        List<Integer> numberList = new ArrayList<>();//销售量集合
        List<LocalDate> dateList = getDateList(begin, end);
            //构造时间
            LocalDateTime start = LocalDateTime.of(begin, LocalTime.MIN);
            LocalDateTime last = LocalDateTime.of(end, LocalTime.MAX);
            List<TopDto> results = reportMapper.getTop10(start, last);
            results.forEach(result->{
                numberList.add(result.getNum());
                nameList.add(result.getDishName());
            });
        return SalesTop10ReportVO.builder()
                .nameList(StringUtils.join(nameList,","))
                .numberList(StringUtils.join(numberList,","))
                .build();
    }

    /**
     * 数据导出
     */
    @Override
    public void export(HttpServletResponse response) {
        //导出数据的时间段
        LocalDate begin = LocalDate.now().minusDays(30);
        LocalDate end = LocalDate.now().minusDays(1);
        //获取最近30天的数据
        BusinessDataVO businessData = workspaceService
                .getBusinessData(LocalDateTime.of(begin, LocalTime.MIN), LocalDateTime.of(end, LocalTime.MAX));
        //读取模版文件
        InputStream in = this.getClass().getClassLoader().getResourceAsStream("template/运营数据报表模板.xlsx");
        try {
            //创建一个Excel对象
            XSSFWorkbook xss = new XSSFWorkbook(in);
            //获取第一个sheet页
            XSSFSheet sheet = xss.getSheetAt(0);
            //给第二行第二列设置值
            sheet.getRow(1).getCell(1).setCellValue(begin+"至"+end);
            //获得第4行
            XSSFRow row = sheet.getRow(3);
            //获取单元格
            row.getCell(2).setCellValue(businessData.getTurnover());
            row.getCell(4).setCellValue(businessData.getOrderCompletionRate());
            row.getCell(6).setCellValue(businessData.getNewUsers());
            row = sheet.getRow(4);
            row.getCell(2).setCellValue(businessData.getValidOrderCount());
            row.getCell(4).setCellValue(businessData.getUnitPrice());
            for (int i = 0; i < 30; i++) {
                LocalDate date = begin.plusDays(i);
                //准备明细数据
                businessData = workspaceService.getBusinessData(LocalDateTime.of(date,LocalTime.MIN), LocalDateTime.of(date, LocalTime.MAX));
                row = sheet.getRow(7 + i);
                row.getCell(1).setCellValue(date.toString());
                row.getCell(2).setCellValue(businessData.getTurnover());
                row.getCell(3).setCellValue(businessData.getValidOrderCount());
                row.getCell(4).setCellValue(businessData.getOrderCompletionRate());
                row.getCell(5).setCellValue(businessData.getUnitPrice());
                row.getCell(6).setCellValue(businessData.getNewUsers());
            }
            //通过输出流将文件下载
            ServletOutputStream out = response.getOutputStream();
            xss.write(out);
            //关闭资源
            in.close();
            out.close();
            xss.close();
        } catch (IOException e) {
            throw new RuntimeException(e);
        }

    }
}
